package evo;

import gui.Console;
import ids.PlacementMove;
import ids.PlacementState;

import java.io.BufferedWriter;
import java.io.File;
import java.io.FileWriter;
import java.io.IOException;

import opt.HillClimbing;

import util.FileReader;
import util.SSIDException;
import util.StopWatch;

public class HCSearch {
	public TechInit tob;

	public BufferedWriter output;

	public Console console;

	public HCSearch(TechInit ti) throws IOException {
		this.tob = ti;
		this.console = new Console();
		this.output = new BufferedWriter(new FileWriter("HCs.stat"));
	}

	public void setConsole(Console console) {
		this.console = console;
	}

	public void search() throws IOException {
		for (int i = 0; i < this.tob.getNumberOfRuns(); i++) {
			HillClimbing hc = new HillClimbing();
			hc.setConsole(this.console);

			PlacementState plcState = new PlacementState();
			PlacementMove plcMove = new PlacementMove();

			this.tob.setSeed(this.tob.getSeed() + i);
			plcState.initialise(tob);

			this.tob.setMove(plcMove);
			this.tob.setState(plcState);

			hc.initialise(this.tob);
			hc.doHillClimbing();

			this.console.println("We have done Hill Climbing");

			plcState = hc.getBestStateSoFar();
			this.console.println(plcState.print());
			this.output.write(plcState.print() + '\n');
		}
		this.output.close();
	}

	public static void main(String[] args) throws IOException, SSIDException {
		FileReader reader = null;
		TechInit tob = null;
		try {
			if (args.length != 5)
				throw new SSIDException(
						"5 parameters are required to run the program.\n");
			else {
				reader = new FileReader(new File(args[0]), new File(args[1]),
						new File(args[2]));
				reader.readTraceFile();
				reader.readTopologyFile();
				reader.readSensorSettings();
				reader.process();
				tob = new TechInit();
				tob.processParamsFile(new File(args[3]));
				tob.setNumberOfRuns(new Integer(args[4]));
				tob.setNodes(reader.getTopology().nodes);
				tob.setSensors(reader.getSensors());
			}
		} catch (SSIDException e) {
			System.err.print(e.getMessage());
			System.err.print(e.getHCSearchUsage());
			System.exit(1);
		}
		HCSearch hillclimbing = new HCSearch(tob);
		System.out.println("Search starts at : " + StopWatch.getCurrentTime());
		hillclimbing.search();
		System.out.println("Search ends at : " + StopWatch.getCurrentTime());
	}
}
